因 JavaScript 在執行階段時,型別可不斷轉換,而這些型別的轉換又可分為 明確的強制轉型
,以及在昨天 Day16 - 嚴格相等 vs 寬鬆相等 中有談到 隱含的強制轉型
,詳細如下:
在程式碼中特意寫出來轉換型別,就稱為 明確的強制轉型
console.log(String(1)); // 1 - 字串型別 => 數字轉字串
當並未在程式碼中明確指出要轉換型別卻轉換了,就稱為 隱含的強制轉型
console.log( 1 + '1'); // 11 - 字串型別
除了 嚴格相等
、寬鬆相等
會轉型外,使用其他的 運算子
也會使值做轉型,以下以加減乘除與取餘數為例:
除字串型別、物件外,與數值相加時,會先轉為數字型別再相加
// 數值 + 數值
console.log(1 + 1); // 2
// 布林 + 數值
console.log(Number(true)); // 1
console.log(1 + true); // 2
// null + 數值
console.log(Number(null)); // 0
console.log(1 + null); // 1
// undefined + 數值
console.log(Number(undefined)); // NaN
console.log(1 + undefined); // NaN
// 包裹物件 + 數值
console.log(new Number(1)); // Number {1}
console.log(1 + new Number(1)); // 2
當字串、物件與數值相加時
.toString()
轉換成字串,而數值也轉換成字串再相加// 字串 + 數值
console.log(1 + '1'); // 11
console.log(1 + 'a'); // 1a
// 物件 + 數值
console.log(1 + [1]); // 11
console.log(1 + {1: 1}); // 1[object Object]
在 Day15 - 優先性與相依性 有談到 優先性
與 相依性
,故在此範例中,都是 +
運算子,優先性相同,而相依性為由左至右,所以會先執行 '英文 60 分、中文 80 分,總分為: ' + english
得出 英文 60 分、中文 80 分,總分為: 60
再與 80
相加
var english = 60;
var chinese = 80;
console.log('英文 60 分、中文 80 分,總分為: ' + english + chinese);
// 英文 60 分、中文 80 分,總分為: 6080
當 undefined、null、布林與字串相加,布林 、null 與 undefined 會使用 String()
,分別轉換成字串後再相加
// undefined + 字串
console.log(undefined + 'a'); // undefined
// null + 字串
console.log(null + 'a'); // nulla
// 布林 + 字串
console.log(true + 'a'); // truea
字串、布林、undefined、null 若與數值相減,會先使用 Number()
轉成數值再做計算
物件則使用 valueOf()
計算或使用 .toString()
先轉為字串再轉數字
console.log(1 - 1); // 0
console.log(1 - '1'); // 0
console.log(1 - 'a'); // NaN
console.log(1 - true); // 0
console.log(1 - false); // 1
console.log(1 - undefined); // 因 undefined 轉數字為 NaN,結果為 NaN
console.log(1 - null); // null 轉數字為 0,1-0 = 1
console.log(1 - {}); // {} 轉成字串為 [object, object] 後再計算 => NaN
console.log(1 - []); // 1
console.log(1 - [1]); // 0
console.log(1 - ['1']); // 0
console.log(1 - new Number(1)); // 0
若乘號其中一個非數值,則會先轉為數值再計算
console.log(2 * 2); // 4
console.log(2 * '2'); // 4
console.log(2 * 'a'); // NaN
console.log(2 * true); // 2
console.log(2 * false); // 0
console.log(2 * null); // null 轉數字為 0,2*0 = 0
console.log(2 * undefined); // 因 undefined 轉數字為 NaN,結果為 NaN
console.log(2 * {}); // NaN
console.log(2 * []); // 0
console.log(2 * [2]); // 4
console.log(2 * ['2']); // 4
console.log(2 * new Number(2)); // 4
若其中一個非數值,則會先轉為數值再計算
console.log(4 / 2); // 2
console.log(0 / 2); // 0
console.log('a' / 2); // NaN
console.log('4' / 2); // 2
console.log(true / 2); // 0.5
console.log(false / 2); // 0
console.log(null / 2); // null 轉數字為 0,0/0=0
console.log(undefined / 2); // 因 undefined 轉數字為 NaN,結果為 NaN
console.log({} / 2); // NaN
console.log([] / 2); // 0
console.log([4] / 2); // 2
console.log(['4'] / 2); // 2
console.log(new Number(4) / 2); // 2
若被除數為 0
,則結果為 Infinity
console.log(4 / 2); // 2
console.log(4 / 0); // 被除數為 0,結果為 Infinity
console.log(4 / 'a'); // NaN
console.log(4 / '2'); // 2
console.log(4 / true); // 4
console.log(4 / false); // false 轉數字為 0,結果為 Infinity
console.log(4 / null); // null 轉數字為 0,結果為 Infinity
console.log(4 / undefined); // 因 undefined 轉數字為 NaN,結果為 NaN
console.log(4 / {}); // NaN
console.log(4 / []); // Infinity
console.log(4 / [2]); // 2
console.log(4 / ['2']); // 2
console.log(4 / new Number(2)); // 2
%
取餘數的規則與除法相似
console.log(5 % 2); // 1
console.log(0 % 2); // 0
console.log('a' % 2); // NaN
console.log('5' % 2); // 1
console.log(true % 2); // 1%2 = 1
console.log(false % 2); // 0%2 = 0
console.log(null % 2); // 0%2 = 0
console.log(undefined % 2); // 因 undefined 轉數字為 NaN,結果為 NaN
console.log({} % 2); // NaN
console.log([] % 2); // 0%2 = 0
console.log([5] % 2); // 1
console.log(['5'] % 2); // 1
console.log(new Number(5) % 2); // 1
若被除數為 0
,則取餘數結果為 NaN
console.log(5 % 2); // 1
console.log(5 % 0); // NaN
console.log(5 % 'a'); // NaN
console.log(5 % '2'); // 1
console.log(5 % true); // 5/1 = 0
console.log(5 % false); // 5/0 = NaN
console.log(5 % null); // 5/0 = NaN
console.log(5 % undefined); // 因 undefined 轉數字為 NaN,結果為 NaN
console.log(5 % {}); // NaN
console.log(5 % []); // NaN
console.log(5 % [2]); // 1
console.log(5 % ['2']); // 1
console.log(5 % new Number(2)); // 1
因 undefined
轉數值會為 NaN
,所以以下舉出一些 NaN
加減乘除所得出的結果
如果其中一個是 NaN
的話,那麼結果會為 NaN
console.log(NaN + 2); // NaN
console.log(NaN - 2); // NaN
console.log(NaN * 2); // NaN
console.log(NaN / 2); // NaN
console.log(2 / NaN); // NaN
console.log(NaN % 2); // NaN
console.log(2 % NaN); // NaN
在加減乘除中,除了 NaN
與 字串型別
相加可得到字串外,其他結果皆為 NaN
console.log(NaN + 1); // NaN
console.log(NaN + '1'); // NaN1 - 字串型別
console.log(NaN + true); // NaN
console.log(NaN + null); // NaN
console.log(NaN + undefined); // NaN
console.log(NaN - 1); // NaN
console.log(NaN - '1'); // NaN
console.log(NaN - true); // NaN
console.log(NaN - null); // NaN
console.log(NaN - undefined); // NaN
console.log(NaN * 1); // NaN
console.log(NaN * '1'); // NaN
console.log(NaN * true); // NaN
console.log(NaN * null); // NaN
console.log(NaN * undefined); // NaN
console.log(NaN / 1); // NaN
console.log(NaN / '1'); // NaN
console.log(NaN / true); // NaN
console.log(NaN / null); // NaN
console.log(NaN / undefined); // NaN